package com.cyh.ebpttoolswar.commmon;

import cn.hutool.core.util.StrUtil;
import com.cyh.ebpttoolswar.entitys.Column;
import com.cyh.ebpttoolswar.entitys.Config;
import com.cyh.ebpttoolswar.entitys.Table;

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

/** @author zth */
public class DbHelper {

  /**
   * 根据表名获得字段名和注释列表
   *
   * @param tableName
   * @return
   */
  public static List<Column> getTableColumns(String tableName, Config config, Connection conn) {
    // 根据表名获得字段名和注释列表
    String sql =
        "select COLUMN_NAME ,DATA_TYPE,COLUMN_COMMENT,COLUMN_KEY from information_schema.columns where table_name = ? and TABLE_SCHEMA = ?";
    PreparedStatement ppst = null;
    List<Column> columns = new ArrayList<Column>();
    Column column = null;
    // boolean primaryFlag = false;
    int primaryNum = 0;
    try {
      // 查询
      ppst = conn.prepareStatement(sql);
      System.out.println("getTableColumns,sql:"+sql);
      ppst.setString(1, tableName);
      ppst.setString(2, config.getTableSchema());
      ResultSet rs = ppst.executeQuery();
        String sql1 = "SELECT ";
        while (rs.next()) {
          column = new Column();
          String columnName = rs.getString("COLUMN_NAME");
          String[] columnNames = columnName.toLowerCase().split("_");
          String columnNamesTmp = columnNames[0];
          if (columnNames.length > 1) {
            // 后边的头字母大写
            for (int i = 1; i < columnNames.length; i++) {
              columnNamesTmp = columnNamesTmp + StrUtil.upperFirst(columnNames[i]);
            }
          }
          column.setName(columnNamesTmp);
          // 设置字段名称
          column.setDbName(columnName);
          // 设置注释
          column.setComment(
                  rs.getString("COLUMN_COMMENT") == null ? "" : rs.getString("COLUMN_COMMENT"));
          column.setNameTopBig(StringHelper.firstToUpper(column.getName()));
          // 设置数据格式
          column.setDbType(rs.getString("DATA_TYPE"));
          // 设置主键
          if ("PRI".equals(rs.getString("COLUMN_KEY"))) {
            column.setPrimary(1);
            //		mc.setPrimaryColumn(column);
            //   primaryFlag = true;
            primaryNum++;
          } else {
            column.setPrimary(0);
          }
          sql1 = sql1 + rs.getString("COLUMN_NAME") + ", ";


//          // 数字型
//          if ("int".equals(column.getDbType())) {
//            column.setJavaType("Integer");
//            column.setJdbcType("INTEGER");
//          } else if ("bigint".equals(column.getDbType())) {
//            column.setJavaType("Long");
//            column.setJdbcType("BIGINT");
//          } else if ("tinyint".equals(column.getDbType())) {
//            column.setJavaType("Short");
//            column.setJdbcType("TINYINT");
//          } else if ("smallint".equals(column.getDbType())) {
//            column.setJavaType("Integer");
//            column.setJdbcType("INTEGER");
//          } else if ("varchar".equals(column.getDbType())) {
//            column.setJavaType("String");
//            column.setJdbcType("VARCHAR");
//          } else if ("text".equals(column.getDbType())) {
//            column.setJavaType("String");
//            column.setJdbcType("LONGVARCHAR");
//          } else if ("char".equals(column.getDbType())) {
//            column.setJavaType("String");
//            column.setJdbcType("CHAR");
//          } else if ("date".equals(column.getDbType()) || "time".equals(column.getDbType())) {
//            column.setJavaType("Date");
//            column.setJdbcType("DATE");
//          } else if ("datetime".equals(column.getDbType())
//                  || "timestamp".equals(column.getDbType())) {
//            column.setJavaType("Date");
//            column.setJdbcType("TIMESTAMP");
//          }
          //		else if("datetime".equals(column.getDbType()) || "date".equals(column.getDbType()) ||
          // "time".equals(column.getDbType())){
          //		column.setJavaType("Date");
          //		column.setJdbcType("DATE");
          //		}else if("timestamp".equals(column.getDbType())){
          //		column.setJavaType("Date");
          //		column.setJdbcType("TIMESTAMP");
          //		}

//          else if ("decimal".equals(column.getDbType())) {
//            column.setJavaType("BigDecimal");
//            column.setJdbcType("DECIMAL");
//          } else if ("float".equals(column.getDbType())) {
//            column.setJavaType("float");
//            column.setJdbcType("FLOAT");
//          } else if ("binary".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("bit".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("blob".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("double".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("enum".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("geometry".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("geometrycollection".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("json".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("linestring".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("longblob".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("longtext".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("mediumint".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("mediumblob".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("mediumtext".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("multilinestring".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("multipoint".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("multipolygon".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("set".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("tinyblob".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("tinyblob".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("tinyint".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("tinytext".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("varbinary".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else if ("year".equals(column.getDbType())) {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          } else {
//            column.setJavaType(column.getDbType());
//            column.setJdbcType(column.getDbType());
//          }

          columns.add(column);
        }
        sql1 = sql1.substring(0,sql1.length()-2)+" FROM "+tableName;
        System.out.println("getTableColumns,sql1:"+sql1);
        ppst = conn.prepareStatement(sql1);
        ResultSet rs1 = ppst.executeQuery();
        int i = 0;
       // rs1.next();
        //设置表JdbcTyp 和java Type
        for (Column tmp : columns) {
          if("[B".equals(rs1.getMetaData().getColumnClassName(i+1))) {
            // 对于byte[] 字段要特殊处理，因为对于byte[]，rs1.getMetaData().getColumnClassName() 的结果“[B”
            // 设置java类型
            tmp.setJavaType("byte[]");
            // 不需要引入包
            tmp.setImportName(null);
            // 设置jdbc类型
            if ("geometry".equals(tmp.getDbType())) {
              tmp.setJdbcType("BIT");
            }else if("geometrycollection".equals(tmp.getDbType())){
                tmp.setJdbcType("BIT");
            }else if("linestring".equals(tmp.getDbType())){
              tmp.setJdbcType("BIT");
            }else if("multilinestring".equals(tmp.getDbType())){
              tmp.setJdbcType("BIT");
            }else if("multipoint".equals(tmp.getDbType())){
              tmp.setJdbcType("BIT");
            }else if("multipolygon".equals(tmp.getDbType())){
              tmp.setJdbcType("BIT");
            }else if("longblob".equals(tmp.getDbType())){
              tmp.setJdbcType("VARCHAR");
            }else{
              tmp.setJdbcType( rs1.getMetaData().getColumnTypeName(i+1));
            }

          }else{
            // 设置要引入的包名，后边会根据报名来设置javaType
            tmp.setImportName(rs1.getMetaData().getColumnClassName(i+1));
            // 设置jdbc类型
            if("DATETIME".equals(rs1.getMetaData().getColumnTypeName(i+1))){
              // 如果是DATETIME 则改为TIMESTAMP
              tmp.setJdbcType("TIMESTAMP");
            }else if("json".equals(tmp.getDbType())){
              tmp.setJdbcType("VARCHAR");
            }else if("int".equals(tmp.getDbType())){
              tmp.setJdbcType("INTEGER");
            }else{
              tmp.setJdbcType( rs1.getMetaData().getColumnTypeName(i+1));
            }

          }
          i++;
        }
        rs1.close();
      for (Column tmp : columns) {
        if(StrUtil.isBlank(tmp.getImportName())){
          continue;
        }
        // 根据"."来分割
        String[] strings = tmp.getImportName().split("\\.");
        if(strings == null){
          continue;
        }
        tmp.setJavaType(strings[strings.length - 1]);

      }
      //            if (!primaryFlag) {
      //                System.out.println("[" + tableName + "]表缺少主键");
      //            } else {
      //                if (primaryNum > 1) {
      //                    System.out.println("[" + tableName + "]表有[" + primaryNum +
      // "]个主键,生成工具暂时不能对多主键进行友好支持");
      //                }
      //            }
      rs.close();
    } catch (SQLException e) {
      e.printStackTrace();
    }
    return columns;
  }

  /**
   * 获取所有表名与表注释
   *
   * @param config
   * @param conn
   * @return
   */
  public static List<Table> getTableList(Config config, Connection conn) {
    List<Table> tables = new ArrayList<Table>();
    String sql =
        "select table_name,table_comment from information_schema.tables where TABLE_SCHEMA = ? ";
    PreparedStatement ppst = null;
    try {
      ppst = conn.prepareStatement(sql);
      ppst.setString(1, config.getTableSchema());
      System.out.println("getTableList,sql:"+sql);
      ResultSet rs = ppst.executeQuery();

      while (rs.next()) {
        Table table = new Table();
        table.setTableName(rs.getString("table_name"));
        table.setTableComment(rs.getString("table_comment"));

        String packageName = "";
        String[] tablesNames = rs.getString("table_name").split("_");
        if (tablesNames.length > 1) {
          for (int i = 1; i < tablesNames.length; i++) {
            packageName = packageName + tablesNames[i];
          }
        } else {
          packageName = tablesNames[0];
        }
        table.setPackageName(packageName);
        tables.add(table);
      }
      rs.close();
    } catch (SQLException e) {
      e.printStackTrace();
    }
    return tables;
  }
}
